package com.heima.leetcode.practice;

/**
 * @author 勾新杰
 * @version 1.0
 * @description: leetcode 7. 整数反转
 * @date 2025/3/4 10:48
 */
public class E7 {

    /**
     * <h3>方法一：直接计算，用long来扩大范围</h3>
     * @param x 待转换的整数
     * @return 转换后的整数
     */
    public int reverse1(int x) {
        int num = Math.abs(x);
        long result = 0;
        while (num > 0) {
            result = result * 10 + num % 10;
            num /= 10;
        }
        if (result > Integer.MAX_VALUE) return 0;
        return x < 0 ? -(int) result : (int) result;
    }

    /**
     * <h3>方法二：计算的同时判断有没有溢出</h3>
     *
     * @param x 待转换的整数
     * @return 转换后的整数
     */
    @SuppressWarnings("all")
    public int reverse2(int x) {
        // 取绝对值对负数的最小值没用，取绝对值后还是负数的最小值
        int result = 0;
        while (x != 0) { // != 0是因为正负都要考虑
            int temp = x % 10;
            x /= 10;
            // 先考虑乘的时候会不会溢出，再考虑加的时候会不会溢出（加之前数字result * 10只有到了Integer.MAX_VALUE / 10的地方才会有可能溢出）
            if (result > Integer.MAX_VALUE / 10 || (result * 10 == Integer.MAX_VALUE - 7 && temp > 7)) return 0;
            if (result < Integer.MIN_VALUE / 10 || (result * 10 == Integer.MIN_VALUE + 8 && temp < -8)) return 0;
            result = result * 10 + temp;
        }
        return result;
    }

    /**
     * <h3>方法二：计算的同时判断有没有溢出</h3>
     *
     * @param x 待转换的整数
     * @return 转换后的整数
     */
    public int reverse3(int x) {
        // 取绝对值对负数的最小值没用，取绝对值后还是负数的最小值
        int result = 0;
        while (x != 0) { // != 0是因为正负都要考虑
            int temp = x % 10;
            x /= 10;
            // 先考虑乘的时候会不会溢出，再考虑加的时候会不会溢出（加之前数字result * 10只有到了Integer.MAX_VALUE / 10的地方才会有可能溢出）
            if (result > Integer.MAX_VALUE / 10 || (result == Integer.MAX_VALUE / 10 && temp > 7)) return 0;
            if (result < Integer.MIN_VALUE / 10 || (result == Integer.MIN_VALUE / 10 && temp < -8)) return 0;
            result = result * 10 + temp;
        }
        return result;
    }

    /**
     * <h3>方法四：思路差不多，单独处理最小值和全部变成正数处理</h3>
     *
     * @param x 待转换的整数
     * @return 转换后的整数
     */
    public int reverse4(int x) {
        boolean positive = x > 0;
        if (x == Integer.MIN_VALUE) return 0;
        x = Math.abs(x);
        int result = 0;
        while (x > 0) {
            int mul10 = result * 10;
            int digit = x % 10;
            // 乘以10后是否会溢出，加上当前位是否会溢出
            if (result > Integer.MAX_VALUE / 10
                    || (mul10 == Integer.MAX_VALUE / 10 && digit > 7)) return 0;
            result = mul10 + digit;
            x /= 10;
        }
        return positive ? result : -result;
    }

    public static void main(String[] args) {
        System.out.println(Integer.MAX_VALUE);
        System.out.println(Integer.MIN_VALUE);
        System.out.println(Math.abs(Integer.MIN_VALUE)); // 还是Integer.MIN_VALUE
        System.out.println(Math.absExact(Integer.MIN_VALUE));
    }
}
